<html>
<head>
<title>GavCoin</title>
<style>
body {
	font-family: Ubuntu, Tahoma, sans;
	background-image: url("backcoin.jpg");
	background-size:   cover;
	background-repeat: no-repeat;
	margin: 0;
}
h1 {
	text-align: center;
	font-size: 26pt;
	color: rgba(0,0,0, 0.75);
}
ul#latest {
	list-style-type: none;
	margin: 0;
	margin-top: 16pt;
	padding: 0;
	border: 16pt rgba(0,0,0, 0.05) solid;
}
ul#latest li {
	padding: 4pt 0pt;
}
ul#latest li:nth-child(even) {
	background-color: rgba(0,0,0, 0.05);
}
span.timestamp {
	width: 13em;
	display: inline-block;
	color: #888;
}
span#gav {
	font-weight: bold;
}
span#eth {
	font-weight: bold;
}
div#top {
	background-color: rgba(0,0,0,0.5);
	color: white;
	padding: 6pt;
	text-shadow: 0px 0px 10px white;
	border-radius: 0 0 6pt 6pt;
}
div#balance {
//	margin-top: 30pt;
	float: left;
}
div#addr {
//	margin-top: 30pt;
//	color: #888;
	float: right;
}
span.xfer {
	color: #888;
}
span.out {
	color: #800;
}
span.mine {
	color: #060;
}
span.in {
	color: #008;
}
span.ind {
	font-weight: bold;
	margin: 0 4pt;
}
span.to, span.from {
	font-weight: normal;
	display: inline-block;
//	width: 25em;
	width: 5em;
}
span.value {
	font-weight: bold;
	width: 5em;
	display: inline-block;
	text-align: right;
}
span.name {
	font-weight: bold;
	font-size: small;
	padding: 0 3pt;
	width: 3em;
	display: inline-block;
	text-align: center;
}
span.xfer span.name {
	font-weight: normal;
}
span.units {
	font-size: small;
	font-weight: bold;
}
li span.units {
	padding: 0 4pt;
}
span.confirms, span.unconfirmed {
	background: #8d9;
	font-size: small;
	margin: -1pt 4pt 4pt 4pt;
	padding: 1pt 3pt 1pt 3pt;
	border: #474 1pt solid;
	border-radius: 4pt;
	float: right;
}
span.unconfirmed {
	background: #f88;
	border-color: #844;
}
input#val {
	width: 8em;
}
input#to {
//	width: 24em;
	width: 10em;
}
div#controls input {
	background: rgba(255,255,255,0.25);
	border: 2pt solid rgba(0,0,0,0.5); 
}
div#controls input.invalid {
	background-color: #fcc;
}
div#controls input.maybevalid {
	background-color: #fec;
}
div#controls button {
	background: rgba(0,0,0,0.25);
	border: 2pt solid rgba(0,0,0,0.5); 
}
button#mine {
	float: right;
}
div#controls button.invalid {
	background: transparent;
	color: rgba(0,0,0,0.25);
	border: 2px solid rgba(0,0,0,0.25);
}
div#controls {
	text-align: center;
	margin-top: 16pt;
	padding: 16pt;
	background-color: rgba(0,0,0, 0.05);
}
div#title {
	margin-top: 10pt;
	margin-left: 18pt;
	font-size: 45pt;
	font-weight: bold;
	text-align: center;
	background-color: rgba(255, 255, 255, 0.5);
	border-radius: 56px;
	display: inline-block;
	padding: 8px;
	padding-right: 24px;
	box-shadow: 0 0 16pt black;
}
div#title img {
	padding-top: 0pt;
	margin-right: 10pt;
}
div#title span {
	color: #430;
	padding-top: 20pt;
	display: inline-block;
	margin-top: -10pt;
}
span#unc {
	color: #fdd;
	font-weight: normal;
}
span#unc span {
	font-weight: bold;
}
</style>
</head>
<body>
<div id="top">
&nbsp;
<div id="balance"><span id="gav">?</span> <span class="units">GAV</span></div>
<div id="addr">?</div>
</div>
<div style="margin: 16pt">
<div style="text-align: center">
<div id="title"><img src="gavcoin.png" width="96" height="96" valign="top"/><span style="font-size: 35pt">GAV</span><span>coin</span></div>
</div>
<ul id="latest">
</ul>
<div id="controls">
	<input id="val" value=""></input> <span class="units">GAV</span>
	to <input id="to"></input>
	<button id="send" onClick="dosend()">send</button>
	<button id="mine" onClick="domine()">mine</button>
</div>
</div>
<script>
var Config = web3.eth.contractFromAbi([{"constant":true,"inputs":[{"name":"service","type":"uint256"}],"name":"lookup","outputs":[{"name":"a","type":"address"}]},{"constant":false,"inputs":[],"name":"kill","outputs":[]},{"constant":false,"inputs":[{"name":"id","type":"uint256"}],"name":"unregister","outputs":[]},{"constant":false,"inputs":[{"name":"id","type":"uint256"},{"name":"service","type":"address"}],"name":"register","outputs":[]}]);

var NameReg = web3.eth.contractFromAbi([{"constant":true,"inputs":[{"name":"_owner","type":"address"}],"name":"getName","outputs":[{"name":"o_name","type":"string32"}]},{"constant":false,"inputs":[{"name":"name","type":"string32"}],"name":"register","outputs":[]},{"constant":true,"inputs":[{"name":"name","type":"string32"}],"name":"addressOf","outputs":[{"name":"addr","type":"address"}]},{"constant":true,"inputs":[{"name":"_name","type":"string32"}],"name":"getAddress","outputs":[{"name":"o_owner","type":"address"}]},{"constant":false,"inputs":[],"name":"unregister","outputs":[]},{"constant":true,"inputs":[{"name":"addr","type":"address"}],"name":"nameOf","outputs":[{"name":"name","type":"string32"}]}]);

var CoinReg = web3.eth.contractFromAbi([{"constant":true,"inputs":[],"name":"count","outputs":[{"name":"r","type":"uint256"}]},{"constant":true,"inputs":[{"name":"i","type":"uint256"}],"name":"info","outputs":[{"name":"addr","type":"address"},{"name":"name","type":"string3"},{"name":"denom","type":"uint256"}]},{"constant":false,"inputs":[{"name":"name","type":"string3"},{"name":"denom","type":"uint256"}],"name":"register","outputs":[]},{"constant":false,"inputs":[],"name":"unregister","outputs":[]}]);

var GavCoin = web3.eth.contractFromAbi([{"constant":true,"inputs":[{"name":"_target","type":"address"},{"name":"_proxy","type":"address"}],"name":"isApprovedFor","outputs":[{"name":"_r","type":"bool"}]},{"constant":true,"inputs":[{"name":"_proxy","type":"address"}],"name":"isApproved","outputs":[{"name":"_r","type":"bool"}]},{"constant":false,"inputs":[{"name":"_from","type":"address"},{"name":"_val","type":"uint256"},{"name":"_to","type":"address"}],"name":"sendCoinFrom","outputs":[]},{"constant":false,"inputs":[],"name":"mine","outputs":[]},{"constant":true,"inputs":[{"name":"_a","type":"address"}],"name":"coinBalanceOf","outputs":[{"name":"_r","type":"uint256"}]},{"constant":false,"inputs":[{"name":"_val","type":"uint256"},{"name":"_to","type":"address"}],"name":"sendCoin","outputs":[]},{"constant":true,"inputs":[],"name":"coinBalance","outputs":[{"name":"_r","type":"uint256"}]},{"constant":false,"inputs":[{"name":"_a","type":"address"}],"name":"approve","outputs":[]}]);

var theNameReg;
var theGavCoin;

var checkto = function() {
	var s = "";
	var to = document.getElementById('to').value;
	var dest;
	if (to.length == 40)
	{
		dest = "0x" + to;
		if (+web3.toDecimal(eth.balanceAt(dest, 0)))
			s = "valid";
		else
			s = "maybevalid";
	}
	else
	{
		var dest = eth.stateAt(nameRegAddr, web3.fromAscii(to), 0);
		if (+web3.toDecimal(dest))
			s = "valid";
		else
		{
			s = "invalid";
			dest = "";
		}
	}
	document.getElementById('to').className = s
	document.getElementById('send').className = (document.getElementById('val').className != "invalid" && document.getElementById('to').className != "invalid") ? "valid" : "invalid";
	return dest;
}

var totalGav = function() {
	var confirmedGav = 0;
	var unconfirmedGav = 0;
	myAddrs.forEach(function(x) { confirmedGav -=- web3.toDecimal(eth.stateAt(gavCoinAddr, x, -1)); unconfirmedGav -=- web3.toDecimal(eth.stateAt(gavCoinAddr, x, 0)); });
	return [confirmedGav, unconfirmedGav];
}

var checkvalue = function() {
	var s = "";
	var amount = +document.getElementById('val').value;
	var tg = totalGav();
	if (amount > 0 && amount <= tg[1])
		if (amount <= tg[0])
			s = "valid";
		else
			s = "maybevalid";
	else
	{
		s = "invalid";
		amount = "";
	}
	document.getElementById('val').className = s;
	document.getElementById('send').className = (document.getElementById('val').className != "invalid" && document.getElementById('to').className != "invalid") ? "valid" : "invalid";
	return (amount * 1000) + '';
}

document.getElementById('val').oninput = checkvalue; 
document.getElementById('to').oninput = checkto;

var dosend = function() {
	var amount = checkvalue();
	var to = checkto();
	if (amount && to)
	{
		var l = +amount;
		eth.accounts.forEach(function(x) {
			if (l)
			{
				var t = +web3.toDecimal(eth.stateAt(gavCoinAddr, x, 0));
				if (t > l)
					t = l;
				if (t)
				{
					eth.transact({'from': x, 'to': gavCoinAddr, 'data': ['send', to, t + ''], 'gas': '2000', 'gasPrice': eth.gasPrice});
					l -= t;
				}
			}
		});
	}
}
var domine = function() {
	eth.transact({ 'to': gavCoinAddr });
}
var pretty = function(x) {
	var ret = eth.stateAt(nameRegAddr, x, 0);
	if (web3.toDecimal(ret) - 0)
		return "<b>" + web3.toAscii(ret) + "</b>";

	return x.substr(2);
}

var oGCA;
var gcTxWatch;
var latest;
var updateGavCoinTxs;

var refresh = function() {
	theNameReg = NameReg(Config().lookup(1));
	theGavCoin = theNameReg.addressOf('GavCoin');

	if (theGavCoin.address != oGCA)
	{
		if (gcTxWatch)
			gcTxWatch.uninstall();
		if (web3.eth.toDecimal(theGavCoin.address))
		{
			gcTxWatch = web3.eth.watch({'max': 15, 'address': theGavCoin.address, 'topics': web3.eth.address });
			gcTxWatch.changed(updateGavCoinTxs);
			return;	// refresh will be called by the above - no need to repeat.
		}
	}
	
	var myAddrs = web3.accounts;
	var cv = checkvalue();
	var ct = checkto();
	var blocksToMine = web3.toDecimal(web3.eth.number) - web3.toDecimal(web3.eth.stateAt(gavCoinAddr, "0x42", 0));
	document.getElementById('mine').className = (blocksToMine ? "valid" : "invalid");
	document.getElementById('mine').innerHTML = blocksToMine == 1 ? "mine" : "mine " + blocksToMine;
	document.getElementById('addr').innerHTML = myAddrs[0].substr(2);
	var confirmedGav = 0;
	var unconfirmedGav = 0;
	myAddrs.forEach(function(x) {
		web3.eth.setBlock(web3.eth.number);
		confirmedGav -=- web3.toDecimal(theGavCoin.coinBalanceOf(x));
		web3.eth.setBlock(0);
		unconfirmedGav -=- web3.toDecimal(theGavCoin.coinBalanceOf(x));
	});
	document.getElementById('gav').innerHTML = (unconfirmedGav > confirmedGav ? confirmedGav / 1000 + '<span id="unc"> (+ <span>' + (unconfirmedGav - confirmedGav) / 1000 + "</span> unconfirmed)</span>" : unconfirmedGav / 1000);
	var lh = document.getElementById("latest");
	lh.innerHTML = "";
	var s = latest.length - 1;
	for (var i = 0; i < latest.length; ++i)
	{
		var l = latest[/*s -*/ i];
		if (+web3.toDecimal(l.to))
		{
			var mine = !+web3.toDecimal(l.input) || web3.toAscii(l.input).substr(0, 4) == "mine";
			var send = web3.toAscii(l.input).substr(0, 4) == "send";
			if (mine || send)
			{
				var dest;
				if (send)
					dest = "0x" + l.input.substr(90, 40);
				var wesent = myAddrs.indexOf(l.from) != -1 || (l.input.length > 96 * 2 + 2 && myAddrs.indexOf(l.origin) != -1);
				var wegot = myAddrs.indexOf(dest) != -1;
				var value = mine ? web3.toDecimal(l.output) * 1000 * ((myAddrs.indexOf(l.coinbase) != -1 ? 1 : 0) + (myAddrs.indexOf(l.from) != -1 ? 1 : 0)) : web3.toDecimal("0x" + l.input.substr(130, 64));
				var age = eth.number - l.number;
//				env.note(eth.number + " " + l.number + " " + age);
				lh.innerHTML = lh.innerHTML + '<li>' +
					'<span class="timestamp">' + new Date(l.timestamp * 1000).toLocaleString() + "</span>" +
					(mine ? '<span class="mine"><span class="name">MINE' : wesent ? wegot ? '<span class="xfer"><span class="name">XFER' : '<span class="out"><span class="name">OUT' : '<span class="in"><span class="name">IN') + '</span>' +
					'<span class="value">' + (value / 1000) + '<span class="units">GAV</span></span>' +
					'' + (mine ? '' : send ? wesent ? wegot ? '' : '<span class="to"><span class="ind">&gt;</span>' + pretty(dest) + '</span>' : '<span class="from"><span class="ind">&lt;</span>' + pretty(l.from) + '</span>' : '') + '</span>' +
					(age ? age > 10 ? '' :
						'<span class="confirms">' + age + ' CONFIRMATIONS</span>' :
						'<span class="unconfirmed">UNCONFIRMED</span>'
					) +
				'</li>';
			}
		}
	}
}

updateGavCoinTxs = function() {
	latest = gcTxWatch.messages();
	refresh();
}

eth.watch("chain").changed(refresh);

</script>
</body>
</html>
